<?php
/**
 * 
 * @authors Liujinbi (857053791@QQ.com)
 * @date    2017-08-02 15:12:25
 * @version $Id$
 */
namespace Wx;

class Xcx
{
	const API_URL_PREFIX = 'https://api.weixin.qq.com';

	const SESSION_KRY_URL = '/sns/jscode2session?appid=%s&secret=%s&js_code=%s&grant_type=authorization_code';
	const ACCESS_TOKEN_URL = '/cgi-bin/token?grant_type=client_credential&appid=%s&secret=%s';
	const SEND_TMP_URL = '/cgi-bin/message/wxopen/template/send?access_token=%s';

	public $access_token = null;
	
	public function __construct($options)
	{
		$this->appid = isset($options['appid'])?$options['appid']:'';
		$this->appsecret = isset($options['appsecret'])?$options['appsecret']:'';
		$this->access_token = self::getAccesstoken();
	}

	public function sessionKey($jscode='',$appid='',$appsecret='')
	{
		$appid=$appid?:$this->appid;
		$appsecret=$appsecret?:$this->appsecret;
		$url=sprintf(self::API_URL_PREFIX.self::SESSION_KRY_URL,$appid,$appsecret,$jscode);
		$re=self::http_get($url);
		$re=$re?json_decode($re,true):false;
		if ($re&&!isset($re['errcode'])) {
			return $re;
		}else{
			$this->errorinfo=$re;
			return false;
		}
	}



	public function getError()
	{
		return $this->errorinfo;
	}

	/**
	 * 获取accessToken {"access_token": "ACCESS_TOKEN", "expires_in": 7200}
	 * @return [type] [description]
	 */
	private function getAccesstoken($appid='',$appsecret=''){
		$contents = self::_file();
		if ($this->access_token) {
			return $this->access_token;
		}elseif ($contents['access_token'] && $contents['access_token']['expires_in'] > time()) {
			$this->access_token = $contents['access_token']['token'];
			return $contents['access_token']['token'];
		}else{
			$appid=$appid?:$this->appid;
			$appsecret=$appsecret?:$this->appsecret;
			$url=sprintf(self::API_URL_PREFIX.self::ACCESS_TOKEN_URL,$appid,$appsecret);
			$re=self::http_get($url);
			$re=$re?json_decode($re,true):false;
			if ($re&&!isset($re['errcode'])) {
				$this->access_token = $re['access_token'];
				$expires_in = strtotime('+7000 seconds');
				$file_arr = array('access_token'=>array('token'=>$this->access_token,'expires_in'=>$expires_in));
				self::merge($contents,$file_arr);
				self::_file($contents);
				return $this->access_token;
			}else{
				$this->access_token = null;
				$this->errorinfo=$re;
				return false;
			}
		}
	}

	/**
	 * 递归合并
	 * @param  [type] &$arr [description]
	 * @param  [type] $n    [description]
	 * @return [type]       [description]
	 */
	private function merge(&$arr,$n){
		foreach ($n as $k => $v) {
			if (is_array($v)) {
				$this->merge($arr[$k],$v);
			}else{
				$arr[$k] = $v;
			}
		}
	}

	/**
	 * 读写文件
	 * @return [type] [description]
	 */
	private function _file($value=array()){
		$filename = __DIR__.'/xcx_config.php';
		if ($value) {
			$str='<?php return '.var_export($value,true) .';';
			file_put_contents($filename,$str);
		}else{
			if (file_exists($filename)) {
				return @include_once($filename);
			}else{
				return false;
			}
		}
	}

	/**
	 *  发送模板消息
	 *  {
		  "touser": "OPENID",  
		  "template_id": "TEMPLATE_ID", 
		  "page": "index",          
		  "form_id": "FORMID",         
		  "data": {
		      "keyword1": {
		          "value": "339208499", 
		          "color": "#173177"
		      }, 
		      "keyword2": {
		          "value": "2015年01月05日 12:30", 
		          "color": "#173177"
		      }, 
		      "keyword3": {
		          "value": "粤海喜来登酒店", 
		          "color": "#173177"
		      } , 
		      "keyword4": {
		          "value": "广州市天河区天河路208号", 
		          "color": "#173177"
		      } 
		  },
		  "emphasis_keyword": "keyword1.DATA" 
		}
	 * @return [type] [description]
	 */
	public function sendTmp($data){
		$url=sprintf(self::API_URL_PREFIX.self::SEND_TMP_URL,$this->access_token);
		$re=self::http_post($url,$data);
		$re=$re?json_decode($re,true):false;
		if ($re&&$re['errcode']==0) {
			return true;
		}else{
			$this->errorinfo=$re;
			return false;
		}
	}

	/**
	 * GET 请求
	 * @param string $url
	 */
	private function http_get($url, $hascurlgetinfo = false){
		$oCurl = curl_init();
		if(stripos($url,"https://")!==FALSE){
			curl_setopt($oCurl, CURLOPT_SSL_VERIFYPEER, FALSE);
			curl_setopt($oCurl, CURLOPT_SSL_VERIFYHOST, FALSE);
			curl_setopt($oCurl, CURLOPT_SSLVERSION, 1); //CURL_SSLVERSION_TLSv1
		}
		curl_setopt($oCurl, CURLOPT_URL, $url);
		curl_setopt($oCurl, CURLOPT_RETURNTRANSFER, 1 );
		$sContent = curl_exec($oCurl);
		$aStatus = curl_getinfo($oCurl);
		curl_close($oCurl);
		if(intval($aStatus["http_code"])==200){
			if ($hascurlgetinfo) {
				return array('curl_exec' => $sContent, 'curl_getinfo'=> $aStatus);
			}else{
				return $sContent;
			}
		}else{
			return false;
		}
	}

	/**
	 * POST 请求
	 * @param string $url
	 * @param array $param
	 * @param boolean $post_file 是否文件上传
	 * @return string content
	 */
	private function http_post($url,$param,$post_file=false){
		$oCurl = curl_init();

		if (class_exists ( '/CURLFile' )) {//php5.5跟php5.6中的CURLOPT_SAFE_UPLOAD的默认值不同  
            curl_setopt ( $oCurl, CURLOPT_SAFE_UPLOAD, true );  
        } else {  
            if (defined ( 'CURLOPT_SAFE_UPLOAD' )) {  
                curl_setopt ( $oCurl, CURLOPT_SAFE_UPLOAD, false );  
            }  
        } 

		if(stripos($url,"https://")!==FALSE){
			curl_setopt($oCurl, CURLOPT_SSL_VERIFYPEER, FALSE);
			curl_setopt($oCurl, CURLOPT_SSL_VERIFYHOST, FALSE);
			curl_setopt($oCurl, CURLOPT_SSLVERSION, 1); //CURL_SSLVERSION_TLSv1
		}
		if (is_string($param) || $post_file) {
			$strPOST = $param;
		} else {
			// $aPOST = array();
			// foreach($param as $key=>$val){
			// 	$aPOST[] = $key."=".urlencode($val);
			// }
			// $strPOST =  join("&", $aPOST);
			$strPOST=json_encode($param);
		}
		curl_setopt($oCurl, CURLOPT_URL, $url);
		curl_setopt($oCurl, CURLOPT_RETURNTRANSFER, 1 );
		curl_setopt($oCurl, CURLOPT_POST,true);
		curl_setopt($oCurl, CURLOPT_POSTFIELDS,$strPOST);
		$sContent = curl_exec($oCurl);
		$aStatus = curl_getinfo($oCurl);
		// print_r($sContent);
		curl_close($oCurl);
		if(intval($aStatus["http_code"])==200){
			return $sContent;
		}else{
			return false;
		}
	}

	public function wxBizDataCrypt($value='', $iv, $sessionKey)
	{
		include_once "wxBizDataCrypt".DS."wxBizDataCrypt.php";
		$pc = new \WXBizDataCrypt($this->appid, $sessionKey);

		$errCode = $pc->decryptData($value, $iv, $data );

		if ($errCode == 0) {
			return ['status'=>1,'info'=>json_decode($data,true)];
		} else {
			return ['status'=>0,'info'=>$errCode];
		}
	}
}